package com.yuw.jdbctest.test2;

import java.sql.*;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

public class DBDriver {
    /**
     * 获取数据库连接对象
     *
     * @return 数据库连接对象
     */
    public Connection getConn() {
        // 2 建立数据库连接
        Connection conn = null;
        try {
            // 0 将数据库的驱动jar包拷入项目的web-info的lib目录中，并引入项目
            // Oracle的驱动类在路径：D:\app\Adminstrator\product\11.2.0\dbhome_1\jdbc\lib\ojdbc6.jar

            // 1 加载数据库驱动
            // 加载数据库驱动类的实例，需要传入的参数有：数据库的连接串（Url）、数据库用户名、数据库访问密码
            // 数据库访问的URL（不同的数据库的URL是固定的，请自行查找即可）
            //String strURL = "jdbc:oracle:thin:@127.0.0.1:1521:orcl";
            /*
             * 解析OracleUrl： jdbc:oracle:thin:@ 这部分是固定格式；
             *
             * @后面是数据库服务器的主机名、ip地址：其中使用127.0.0.1 表示数据库服务器是本机；或者使用 localhost表示本机 1521
             * 表示Oracle客户端监听程序的端口号； orcl是Oracle数据库的实例名（等价认为是数据库名）
             */

            // 数据库的驱动类的包路径名
            String strURL = "jdbc:mysql://localhost/mybatis201712?useUnicode=true&characterEncoding=UTF-8";
            /*
             * 解析OracleUrl： jdbc:oracle:thin:@ 这部分是固定格式；
             *
             * @后面是数据库服务器的主机名、ip地址：其中使用127.0.0.1 表示数据库服务器是本机；或者使用 localhost表示本机 1521
             * 表示Oracle客户端监听程序的端口号； orcl是Oracle数据库的实例名（等价认为是数据库名）
             */
            // 用户名和密码
            String strUserName = "root";
            String strUserPsw = "root";
            // 数据库的驱动类的包路径名
            String strDBDriver = "com.mysql.jdbc.Driver";

            // 使用反射的方式创建数据库驱动类的实例，各个数据库驱动类的名字是固定的，请自行查找；
            Class.forName(strDBDriver);

            conn = DriverManager.getConnection(strURL, strUserName, strUserPsw);
        } catch (Exception e) {
            // 异常处理
            System.out.println("jdbc获取数据库连接异常：");
            e.printStackTrace();
        }

        return conn;
    }

    /**
     * 基于jdbc查询操作
     *
     * @param strSql 查询sql语句
     * @return ResultSet结果集
     */
    @Deprecated
    public ResultSet query(String strSql) {
        // 返回对象，查询结果集
        ResultSet rs = null;
        try {
            // 4 执行SQL语句
            // 需要使用Statement查询器对象进行sql语句执行
            // 创建一个conn对象的查询器Statement
            // 括号中的参数是为了可以重置ResultSet的游标的位置
            Statement st = getConn().createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
            // 使用查询器Statement，执行sql语句
            rs = st.executeQuery(strSql);
        } catch (Exception e) {
            // 异常处理
            System.out.println("jdbc查询异常：");
            e.printStackTrace();
        }
        return rs;
    }

    /**
     * 基于jdbc查询操作
     *
     * @param strSql 查询sql语句
     * @return List+Map类型的结果集
     */
    public List<Map<String, Object>> queryListMap(String strSql) {
        // 返回对象List
        List<Map<String, Object>> lst = new ArrayList<>();

        // 获取查询结果集ResultSet
        // 返回对象，查询结果集

        // 将查询结果集ResultSet中的数据 拷贝到 List+Map的数据结构中

        try (Connection conn = getConn();
             // 4 执行SQL语句
             // 需要使用Statement查询器对象进行sql语句执行
             // 创建一个conn对象的查询器Statement
             // 括号中的参数是为了可以重置ResultSet的游标的位置
             Statement st = conn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY);
             // 使用查询器Statement，执行sql语句
             ResultSet rs = st.executeQuery(strSql);) {
            // 将ResultSet的遍历的下标位置从最后，重置到初始位置
            rs.beforeFirst();
            // 使用元数据获取每一行的类信息数据
            ResultSetMetaData rsmd = rs.getMetaData();
            // 获取列数
            int columnCount = rsmd.getColumnCount();
            // 自动遍历每一行数据的的各个列的值
            while (rs.next()) {
                // 创建一个Map对象，用于存储每一行的数据的列的值（列名和列值构成键值对）
                Map<String, Object> map = new LinkedHashMap<>();
                // 使用Resultset的元数据遍历每一行的列数据
                for (int i = 1; i <= columnCount; i++) {
                    // 获取当前列的名字
                    String strColmnName = rsmd.getColumnLabel(i);
                    // 获取当前列的值
                    Object objColmnValue = rs.getObject(strColmnName);
                    // 列名-列值 键值对放到每一行的map中
                    map.put(strColmnName, objColmnValue);
                }
                // 将每一行的map存入List中，List中的每个map表示是一行数据
                lst.add(map);
            }
        } catch (SQLException e) {
            // 异常处理
            System.out.println("jdbc查询异常：");
            e.printStackTrace();
        }
        // 返回值
        return lst;
    }

}
